#include "meshTypeFunctions.hpp"
#include <catch2/catch_test_macros.hpp>
#include <catch2/catch_approx.hpp>
#include <iostream>

using Catch::Approx;
using namespace hms;

TEST_CASE("RectCells"){
	ArrayXs xCoords (4), yCoords (3), xCopy, yCopy;

	xCoords << -1, 0, 2, 6;
	yCoords << -2, 0, 1;
	xCopy = xCoords;
	yCopy = yCoords;

	RectMesh mesh { std::move(xCopy), std::move(yCopy) };

	SECTION("areas"){
		/* bottom row (ghosts) */
		// REQUIRE( mesh.cells().areas()(0) == Approx(2) );
		REQUIRE( mesh.cells().areas()(1) == Approx(2) );
		REQUIRE( mesh.cells().areas()(2) == Approx(4) );
		REQUIRE( mesh.cells().areas()(3) == Approx(8) );
		// REQUIRE( mesh.cells().areas()(4) == Approx(8) );
		
		/* second row, holds bottom domain cells */
		REQUIRE( mesh.cells().areas()( 5) == Approx(2) );
		REQUIRE( mesh.cells().areas()( 6) == Approx(2) );
		REQUIRE( mesh.cells().areas()( 7) == Approx(4) );
		REQUIRE( mesh.cells().areas()( 8) == Approx(8) );
		REQUIRE( mesh.cells().areas()( 9) == Approx(8) );

		/* third row, holds top domain cells */
		REQUIRE( mesh.cells().areas()(10) == Approx(1) );
		REQUIRE( mesh.cells().areas()(11) == Approx(1) );
		REQUIRE( mesh.cells().areas()(12) == Approx(2) );
		REQUIRE( mesh.cells().areas()(13) == Approx(4) );
		REQUIRE( mesh.cells().areas()(14) == Approx(4) );

		/* top row (ghosts) */
		// REQUIRE( mesh.cells().areas()(15) == Approx(1) );
		REQUIRE( mesh.cells().areas()(16) == Approx(1) );
		REQUIRE( mesh.cells().areas()(17) == Approx(2) );
		REQUIRE( mesh.cells().areas()(18) == Approx(4) );
		// REQUIRE( mesh.cells().areas()(19) == Approx(4) );
	}
	SECTION("circumferences"){
		/* bottom row (ghosts) */
		REQUIRE( mesh.cells().circumfs()(1) == Approx( 6) );
		REQUIRE( mesh.cells().circumfs()(2) == Approx( 8) );
		REQUIRE( mesh.cells().circumfs()(3) == Approx(12) );
		
		/* second row, holds bottom domain cells */
		REQUIRE( mesh.cells().circumfs()( 5) == Approx( 6) );
		REQUIRE( mesh.cells().circumfs()( 6) == Approx( 6) );
		REQUIRE( mesh.cells().circumfs()( 7) == Approx( 8) );
		REQUIRE( mesh.cells().circumfs()( 8) == Approx(12) );
		REQUIRE( mesh.cells().circumfs()( 9) == Approx(12) );

		/* third row, holds top domain cells */
		REQUIRE( mesh.cells().circumfs()(10) == Approx( 4) );
		REQUIRE( mesh.cells().circumfs()(11) == Approx( 4) );
		REQUIRE( mesh.cells().circumfs()(12) == Approx( 6) );
		REQUIRE( mesh.cells().circumfs()(13) == Approx(10) );
		REQUIRE( mesh.cells().circumfs()(14) == Approx(10) );

		/* top row (ghosts) */
		REQUIRE( mesh.cells().circumfs()(16) == Approx( 4) );
		REQUIRE( mesh.cells().circumfs()(17) == Approx( 6) );
		REQUIRE( mesh.cells().circumfs()(18) == Approx(10) );
	}
	SECTION("centroids"){
		/* bottom row (ghosts) */
		REQUIRE( mesh.cells().centroids().col( 1).isApprox( Vector2s{-0.5,-3.0} ) );
		REQUIRE( mesh.cells().centroids().col( 2).isApprox( Vector2s{ 1.0,-3.0} ) );
		REQUIRE( mesh.cells().centroids().col( 3).isApprox( Vector2s{ 4.0,-3.0} ) );
		
		/* second row, holds bottom domain cells */
		REQUIRE( mesh.cells().centroids().col( 5).isApprox( Vector2s{-1.5,-1.0} ) );
		REQUIRE( mesh.cells().centroids().col( 6).isApprox( Vector2s{-0.5,-1.0} ) );
		REQUIRE( mesh.cells().centroids().col( 7).isApprox( Vector2s{ 1.0,-1.0} ) );
		REQUIRE( mesh.cells().centroids().col( 8).isApprox( Vector2s{ 4.0,-1.0} ) );
		REQUIRE( mesh.cells().centroids().col( 9).isApprox( Vector2s{ 8.0,-1.0} ) );

		/* third row, holds top domain cells */
		REQUIRE( mesh.cells().centroids().col(10).isApprox( Vector2s{-1.5, 0.5} ) );
		REQUIRE( mesh.cells().centroids().col(11).isApprox( Vector2s{-0.5, 0.5} ) );
		REQUIRE( mesh.cells().centroids().col(12).isApprox( Vector2s{ 1.0, 0.5} ) );
		REQUIRE( mesh.cells().centroids().col(13).isApprox( Vector2s{ 4.0, 0.5} ) );
		REQUIRE( mesh.cells().centroids().col(14).isApprox( Vector2s{ 8.0, 0.5} ) );

		/* top row (ghosts) */
		REQUIRE( mesh.cells().centroids().col(16).isApprox( Vector2s{-0.5, 1.5} ) );
		REQUIRE( mesh.cells().centroids().col(17).isApprox( Vector2s{ 1.0, 1.5} ) );
		REQUIRE( mesh.cells().centroids().col(18).isApprox( Vector2s{ 4.0, 1.5} ) );
	}
}